﻿using System;
using System.Reflection;
using MugenInjection.Attributes;
using MugenInjection.Core;
using MugenInjection.Delegates;
using MugenInjection.Scope;

namespace MugenInjection.Interface
{
    /// <summary>
    /// Contains configuration options for specified <see cref="IInjector"/>.
    /// </summary>
    public interface IInjectorSettings
    {
        /// <summary>
        /// Gets or sets value, if <c>true</c>Throw error if binding provider return null result; otherwise, <c>false</c>. (Default is <c>true</c>).
        /// </summary>
        bool ThrowErrorForNullableBinding { get; set; }

        /// <summary>
        /// Gets or sets value, if <c>false</c> and the binding is not found in the current container, but it found in the parent, activate the binding in the current container; otherwise <c>true</c>.
        /// </summary>
        bool UseParentToResolve { get; set; }

#if !NOLOADASSEMBLY
        /// <summary>
        /// Gets or sets value that indicates whether the automatic loading of the module. (Default is <c>true</c>).
        /// </summary>
        bool IsAutoLoadModuleEnabled { get; set; }

        /// <summary>
        /// Gets or sets an attribute that used to automatically load the <see cref="InjectorModule"/>. (Default <see cref="AutoLoadModuleAttribute"/>)
        /// </summary>
        Type AttributeForAutoLoadModule { get; set; }
#endif

#if SCANASSEMBLY
        /// <summary>
        /// Gets or sets value if <c>true</c> throw an error if unable to load the assembly. (Default is <c>true</c>).
        /// </summary>
        bool ThrowErrorIfNotLoadAssembly { get; set; }

        /// <summary>
        /// Gets or sets value that indicates whether the automatic scan of the files, default is <c>true</c>.
        /// </summary>
        bool IsAutoScanAssembly { get; set; }
#endif

        /// <summary>
        /// Gets or sets an attribute specifies where to use injection. (Default <see cref="InjectAttribute"/>)
        /// </summary>
        Type AttributeForInject { get; set; }

        /// <summary>
        /// Gets or sets a factory to create <see cref="IActivator"/>.
        /// </summary>
        Func<IActivator> DefaultActivatorFactory { get; set; }

        /// <summary>
        /// Gets or sets a factory to create <see cref="IConstructorResolver"/>.
        /// </summary>
        Func<IConstructorResolver> DefaultConstructorResolverFactory { get; set; }

        /// <summary>
        /// Gets or sets a factory to create <see cref="ScopeLifecycleBase"/>. Default is <see cref="TransientScopeLifecycle"/>.
        /// </summary>
        Func<IScopeLifecycle> DefaultScopeLifecycleFactory { get; set; }

        /// <summary>
        /// Occurs when a setting value changes.
        /// </summary>
        event Action<string, object> SettingChanged;

        /// <summary>
        /// Creates a new object that is a copy of the current instance.
        /// </summary>
        /// <returns>
        /// A new object that is a copy of this instance.
        /// </returns>
        IInjectorSettings Clone();
    }
}